import re
import pyecharts.options as opts
from pyecharts.charts import Line, Grid
import yaml
import logging.config
from configs.config import global_var
from pyecharts.charts import Bar
from pyecharts.faker import Faker


class Logger:
    def __init__(self):
        # 用于存储图表文件的地址
        self.visPath = global_var.saving_address + 'vis_final'
        # 导入并读取配置文件
        self.yamlPath = global_var.loading_address + "configs/loggingconfig.yaml"
        self.configFile = open(self.yamlPath, 'r', encoding='utf-8')
        self.dict = yaml.load(self.configFile, Loader=yaml.FullLoader)  # 用load方法转字典
        # 修改配置文件中的地址信息
        # print(self.dict)
        self.dict['handlers']['fileHandler_train']['filename'] \
            = global_var.saving_address + 'eval/log_info/train_record.log'
        self.dict['handlers']['fileHandler_test']['filename'] \
            = global_var.saving_address + 'eval/log_info/test_record.log'
        # 导入配置到logger
        logging.config.dictConfig(self.dict)
        self.train_log = logging.getLogger('train_log')  # 生成一个train_log
        self.test_log = logging.getLogger('test_log')  # 生成一个train_log

    def load(self, path=None, mode='t'):
        if mode == 't':
            # 导入load
            epoch = []
            loss = []
            max_dis = []
            # print(self.dict['handlers']['fileHandler_train']['filename'])
            with open(path, 'r') as f:
                lines = f.readlines()
                for line in lines:
                    epoch.append(float(re.search(r'epoch:(.*?)loss', line).group(1)))
                    loss.append(float(re.search(r'loss:(.*?)max_dis', line).group(1)))
                    max_dis.append(float(re.search(r'max_dis:(.*?)\n', line).group(1)))
            return epoch, loss, max_dis

    def visualization(self):
        train_epoch, train_loss, train_max = \
            self.load(self.dict['handlers']['fileHandler_train']['filename'])
        test_epoch, test_loss, test_max = \
            self.load(self.dict['handlers']['fileHandler_test']['filename'])
        # 绘制折线图
        l1 = (
            Line()
            .add_xaxis(train_epoch)
            .add_yaxis("train_loss", train_loss, is_smooth=True,
                       symbol_size=8,
                       is_hover_animation=False,
                       label_opts=opts.LabelOpts(is_show=False),
                       linestyle_opts=opts.LineStyleOpts(width=1.5)
                       )
            .add_yaxis("test_loss", test_loss, is_smooth=True,
                       symbol_size=8,
                       is_hover_animation=False,
                       label_opts=opts.LabelOpts(is_show=False),
                       linestyle_opts=opts.LineStyleOpts(width=1.5)
                       )
            .set_global_opts
                (
                title_opts=opts.TitleOpts(
                    title="基于Res50的分类结果",
                    pos_left="center"),
                tooltip_opts=opts.TooltipOpts(trigger="axis"),
                datazoom_opts=[
                    opts.DataZoomOpts(
                        is_show=True,
                        is_realtime=True,
                        start_value=30,
                        end_value=70,
                        xaxis_index=[0, 1],
                    )],
                xaxis_opts=opts.AxisOpts(
                    name='epoch',
                    type_="category",
                    boundary_gap=False,
                    axisline_opts=opts.AxisLineOpts(is_on_zero=True),
                ),
                yaxis_opts=opts.AxisOpts(name="mse损失"),
                legend_opts=opts.LegendOpts(pos_left="left"),
                toolbox_opts=opts.ToolboxOpts(
                    is_show=True,
                    feature={
                        "dataZoom": {"yAxisIndex": "none"},
                        "restore": {},
                        "saveAsImage": {},
                    },
                ),
            )
        )
        l2 = (
            Line()
            .add_xaxis(train_epoch)
            .add_yaxis("train_max_dis", train_max, is_smooth=True,
                       symbol_size=8,
                       is_hover_animation=False,
                       label_opts=opts.LabelOpts(is_show=False),
                       linestyle_opts=opts.LineStyleOpts(width=1.5)
                       )
            .add_yaxis("test_max_dis", test_max, is_smooth=True,
                       symbol_size=8,
                       is_hover_animation=False,
                       label_opts=opts.LabelOpts(is_show=False),
                       linestyle_opts=opts.LineStyleOpts(width=1.5)
                       )
            .set_global_opts
                (
                tooltip_opts=opts.TooltipOpts(trigger="axis"),
                datazoom_opts=[
                    opts.DataZoomOpts(
                        is_show=True,
                        is_realtime=True,
                        start_value=30,
                        end_value=70,
                        xaxis_index=[0, 1],
                    )],
                xaxis_opts=opts.AxisOpts(
                    name='epoch',
                    type_="category",
                    boundary_gap=False,
                    axisline_opts=opts.AxisLineOpts(is_on_zero=True),
                ),
                yaxis_opts=opts.AxisOpts(name="最大顶点距离"),
                legend_opts=opts.LegendOpts(pos_left='left', pos_top="48%"),
                toolbox_opts=opts.ToolboxOpts(
                    is_show=True,
                    feature={
                        "dataZoom": {"yAxisIndex": "none"},
                        "restore": {},
                        "saveAsImage": {},
                    },
                ),
            )
        )
        (
            Grid(init_opts=opts.InitOpts(width="1024px", height="768px"))
            .add(chart=l1, grid_opts=opts.GridOpts(pos_left=50, pos_right=50, height="35%"))
            .add(
                chart=l2,
                grid_opts=opts.GridOpts(pos_left=50, pos_right=50, pos_top="56%", height="35%"),
            )
            .render(global_var.saving_address + "vis_final/training_history_record.html")
        )


